package demo17

// chain
import "fmt"

// 责任链设计模式

type Manager interface {
	HaveRight(money int) bool
	HandleFeeRequest(name string, money int) bool
}

// 结构体包含接口的好处
// 可以 构造该结构体 里面Manager可以不同，同时都可以有该结构体完成调用
// 同时RequestChain 实现了接口
type RequestChain struct {
	Manager
	successor *RequestChain
}

// successor 可以包含一个节点
func (r *RequestChain) SetSuccessor(m *RequestChain) {
	r.successor = m
}

func (r *RequestChain) HandleFeeRequest(name string, money int) bool {
	if r.Manager.HaveRight(money) {
		return r.Manager.HandleFeeRequest(name, money)
	}
	// 如果有子节点的话一起执行
	if r.successor != nil {
		return r.successor.HandleFeeRequest(name, money)
	}
	// 都不满足条件的话返回false
	return false
}

// 条件逻辑
func (r *RequestChain) HaveRight(money int) bool {
	return true
}

// 实例
type ProjectManager struct{}

func NewProjectManagerChain() *RequestChain {
	return &RequestChain{
		Manager: &ProjectManager{},
	}
}

// 实例条件
func (*ProjectManager) HaveRight(money int) bool {
	return money < 500
}

func (*ProjectManager) HandleFeeRequest(name string, money int) bool {
	if name == "bob" {
		// 如果有该人的话
		fmt.Printf("Project manager permit %s %d fee request\n", name, money)
		return true
	}
	// 没有的话
	fmt.Printf("Project manager don't permit %s %d fee request\n", name, money)
	return false
}

type DepManager struct{}

func NewDepManagerChain() *RequestChain {
	return &RequestChain{
		Manager: &DepManager{},
	}
}

func (*DepManager) HaveRight(money int) bool {
	return money < 5000
}
func (*DepManager) HandleFeeRequest(name string, money int) bool {
	if name == "tom" {
		fmt.Printf("Dep manager permit %s %d fee request\n", name, money)
		return true
	}
	fmt.Printf("Dep manager don't permit %s %d fee request\n", name, money)
	return false
}

type GeneralManger struct{}

func NewGeneralManger() *RequestChain {
	return &RequestChain{
		Manager: &GeneralManger{},
	}
}

func (*GeneralManger) HandleFeeRequest(name string, money int) bool {
	if name == "ada" {
		fmt.Printf("General manager  permit %s %d fee request\n", name, money)
		return true
	}
	fmt.Printf("General manager don't permit %s %d fee request\n", name, money)
	return false
}

func (*GeneralManger) HaveRight(money int) bool {
	return true
}
